<?php
/**
 * Created by PhpStorm.
 * User: pc
 * Date: 2024/1/26
 * Time: 15:53
 */

namespace app\common\service;


use app\common\helper\TreeHelper;
use yii\db\ActiveQuery;
use yii\db\Expression;
use yii\helpers\ArrayHelper;

class OptionsHandel
{
    private $class ;
    private $field_id ;
    private $filed_name ;
    private $ext ;
    private $where ;
    private $type ;
    private $pid ;
    private $options;

    /**
     * @param mixed $options
     */
    public function setOptions($options)
    {
        $this->options = $options;
    }

    /**
     * @return mixed
     */
    public function getPid()
    {
        return $this->pid;
    }

    /**
     * @param mixed $pid
     */
    public function setPid($pid)
    {
        $this->pid = $pid;
    }

    /**
     * @return mixed
     */
    public function getType()
    {
        return $this->type;
    }

    /**
     * @param mixed $type
     */
    public function setType($type)
    {
        $this->type = $type;
    }

    /**
     * @return mixed
     */
    public function getWhere()
    {
        return $this->where;
    }

    /**
     * @param mixed $where
     */
    public function setWhere($where)
    {
        if($where){
            $this->where = $where;
        }
    }

    /**
     * @return mixed
     */
    public function getExt()
    {
        return $this->ext;
    }

    /**
     * @param mixed $ext
     */
    public function setExt($ext)
    {
        $this->ext = $ext;
    }

    /**
     * @return mixed
     */
    public function getFieldId()
    {
        return $this->field_id;
    }

    /**
     * @param mixed $field_id
     */
    public function setFieldId($field_id)
    {
        $this->field_id = $field_id;
    }

    /**
     * @return mixed
     */
    public function getFiledName()
    {
        return $this->filed_name;
    }

    /**
     * @param mixed $filed_name
     */
    public function setFiledName($filed_name)
    {
        $this->filed_name = $filed_name;
    }

    /**
     * @return mixed
     */
    public function getClass()
    {
        return $this->class;
    }

    /**
     * @param mixed $class
     */
    public function setClass($class)
    {
        $this->class = $class;
    }

    public function __construct($map_item)
    {
        if($map_item instanceof OptionMapItem){
            $this->setClass($map_item->getClass());
            $this->setFieldId($map_item->getId());
            $this->setFiledName($map_item->getName());
            $this->setExt($map_item->getExtend());
            $this->setWhere($map_item->getWhere());
            $this->setType($map_item->getType());
            $this->setPid($map_item->getPid());
            if($map_item->getOptions()){
                $this->setOptions($map_item->getOptions());
            }
        }else{
            $class = ArrayHelper::getValue($map_item,'class');
            $field_id = ArrayHelper::getValue($map_item,'id');
            $filed_name = ArrayHelper::getValue($map_item,'name');
            $ext = ArrayHelper::getValue($map_item,'extend');
            $where = ArrayHelper::getValue($map_item,'where');
            $type = ArrayHelper::getValue($map_item,'type');
            $pid = ArrayHelper::getValue($map_item,'pid');
            $this->setClass($class);
            $this->setFieldId($field_id);
            $this->setFiledName($filed_name);
            $this->setExt($ext);
            $this->setWhere($where);
            $this->setType($type);
            $this->setPid($pid);
        }
    }

    public function getOptions(){
        if($this->options){
            return $this->options;
        }
        /**
         * @var $query ActiveQuery
         */
        $class = $this->getClass();
        $query = $class::find()->alias("t");
        $query = $this->dealQueryByType($query);
        $where = $this->getWhere();
        if($where && !is_callable($where)){
            $query->andWhere($where);
        }
//        echo $query->createCommand()->rawSql;exit();
//        try{
            $list = $query->asArray()->all();
//        }catch (\Throwable $e){
//            var_dump($query);
//            echo $query->createCommand()->rawSql;exit();
//        }

        if($list){
            return $this->dealOptionsByType($list);
        }
        return [];
    }

    public function dealQueryByType($query){
        $type = $this->getType();
        $field_id = $this->getFieldId();
        $filed_name = $this->getFiledName();
        $pid = $this->getPid();
        if($type == 'tree'){
            $query->select([
                new Expression("{$field_id} as id"),
                new Expression("{$field_id} as value"),
                new Expression("{$filed_name} as name"),
                new Expression("{$filed_name} as title"),
                new Expression("{$pid} as pid"),
            ]);
        }else{
            $query->select([
                new Expression("{$field_id} as id"),
                new Expression("{$filed_name} as name"),
            ]);
        }
        return $query;
    }

    public function dealOptionsByType($list){
        $options = [];
        $type = $this->getType();
        if($list){
            if($type == 'tree'){
                $options = TreeHelper::generateTree($list);
            }else{
                $options = ArrayHelper::map($list,'id','name');
                if(!empty($this->getExt())){
                    $options = ArrayHelper::merge($this->getExt(),$options);
                }
            }
        }
        return $options;
    }

    public static function createInstance($map_item){
        return new self($map_item);
    }
}